package com.example.sbbsec.quartz.executor;

import com.example.sbbsec.quartz.entity.executor.JobExecutorInfo;
import org.quartz.DisallowConcurrentExecution;
import org.quartz.Job;
import org.quartz.JobDetail;
import org.quartz.JobExecutionContext;
import org.quartz.JobExecutionException;
import org.quartz.Trigger;
import org.slf4j.Logger;

import java.io.Serializable;
import java.time.Duration;
import java.time.Instant;

import static org.slf4j.LoggerFactory.getLogger;

/**
 * job
 *
 * @author lowe.yang
 * @date 2019-01-25 16:31
 */
@DisallowConcurrentExecution
public abstract class AbstractJobExecutor implements Job, Serializable {
    private static final Logger LOGGER = getLogger(AbstractJobExecutor.class);

    @Override
    public void execute(JobExecutionContext context) throws JobExecutionException {
        //构建实体
        final JobExecutorInfo jobExecutorInfo = new JobExecutorInfo();
        buildJobHandlerInfo(context, jobExecutorInfo);

        final String jobName = jobExecutorInfo.getJobName();
        final String jobGroup = jobExecutorInfo.getJobGroup();
        final String description = jobExecutorInfo.getDescription();
        LOGGER.info("任务开始执行,任务组:{},任务名称:{},任务描述:{}", jobGroup, jobName, description);
        final Instant begin = Instant.now();

        //执行
        handler(jobExecutorInfo);

        LOGGER.info("任务执行结束,任务组:{},任务名称:{},任务描述:{},耗时:{}毫秒", jobName, jobGroup, description
                , Duration.between(begin, Instant.now()).toMillis());
    }

    /**
     * 实体转换
     *
     * @param context JobExecutionContext
     */
    private void buildJobHandlerInfo(JobExecutionContext context, JobExecutorInfo jobExecutorInfo) {
        //job详情
        final JobDetail jobDetail = context.getJobDetail();
        final Trigger trigger = context.getTrigger();

        //任务名称
        jobExecutorInfo.setJobName(trigger.getJobKey().getName());
        //任务组
        jobExecutorInfo.setJobGroup(trigger.getJobKey().getGroup());
        //任务描述
        jobExecutorInfo.setDescription(jobDetail.getDescription());
        //数据
        jobExecutorInfo.setData(jobDetail.getJobDataMap());
    }

    /**
     * 具体job执行类
     * 子类需继承
     */
    protected abstract void handler(JobExecutorInfo jobExecutorInfo);

}
